package com.lykj.modules.job.jobhandler;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.lykj.common.cache.ParamCache;
import com.lykj.core.tool.utils.DateUtil;
import com.lykj.job.core.context.LykjJobHelper;
import com.lykj.job.core.handler.annotation.LykjJob;
import com.lykj.modules.shop.entity.*;
import com.lykj.modules.shop.service.UserBillService;
import com.lykj.modules.shop.service.UserBonusService;
import com.lykj.modules.shop.service.UserOrderService;
import com.lykj.modules.system.entity.User;
import com.lykj.modules.system.service.UserService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import java.math.BigDecimal;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Component
public class ShsyTaskJob {
	private static Logger logger = LoggerFactory.getLogger(ShsyTaskJob.class);

	// 超限金额
	public static Map<Integer, BigDecimal> limit = new HashMap<>();
	// 复购金额
	public static Map<Integer, BigDecimal> repeat = new HashMap<>();
	// 极差值
	public static Map<Integer, BigDecimal> value = new HashMap<>();
	// 自消费额度
	public static Map<Integer, BigDecimal> onw = new HashMap<>();
	// 团队业绩
	public static Map<Integer, BigDecimal> team = new HashMap<>();
	// 升级对应级别会员数量
	public static Map<Integer, Integer> num = new HashMap<>();

	private final UserService userService;
	private final UserOrderService userOrderService;
	private final UserBonusService userBonusService;
	private final UserBillService userBillService;

	public ShsyTaskJob(UserService userService, UserOrderService userOrderService, UserBonusService userBonusService, UserBillService userBillService) {
		this.userService = userService;
		this.userOrderService = userOrderService;
		this.userBonusService = userBonusService;
		this.userBillService = userBillService;
	}

//	@LykjJob("testJobHandler")
	public void testJobHandler() {
		JSONArray memberSystemRule = JSONArray.parseArray(ParamCache.getValue("member.system.rule"));
		if (memberSystemRule instanceof JSONArray) {
			memberSystemRule.stream().forEach(x -> {
				JSONObject object = (JSONObject) x;
				num.put(object.getInteger("no"), object.getInteger("num"));
				repeat.put(object.getInteger("no"), object.getBigDecimal("repeat"));
				limit.put(object.getInteger("no"), object.getBigDecimal("limit"));
				onw.put(object.getInteger("no"), object.getBigDecimal("onw"));
				team.put(object.getInteger("no"), object.getBigDecimal("team"));
				value.put(object.getInteger("no"), object.getBigDecimal("value"));
			});
		}
		System.out.println("num:" + num.toString());
		System.out.println("repeat:" + repeat.toString());
		System.out.println("limit:" + limit.toString());
		System.out.println("onw:" + onw.toString());
		System.out.println("team:" + team.toString());
		System.out.println("value:" + value.toString());
	}

	/**--------------------------------------------------------------------------红包资格定时任务-----------------------------------------------------------------------------------------**/

	/**
	 * TODO 红包资格定时任务 每5分钟执行一次
	 */
//	@LykjJob("bonusStatusJobHandler")
	@Scheduled(cron = "0 */5 * * * ?")
	public void bonusStatusJobHandler() throws Exception {
		LykjJobHelper.log("红包资格定时任务。。。。。。");
		// 获取相应规则
		JSONArray memberSystemRule = JSONArray.parseArray(ParamCache.getValue("member.system.rule"));
		if (memberSystemRule instanceof JSONArray) {
			memberSystemRule.stream().forEach(x -> {
				JSONObject object = (JSONObject) x;
				num.put(object.getInteger("no"), object.getInteger("num"));
				repeat.put(object.getInteger("no"), object.getBigDecimal("repeat"));
				limit.put(object.getInteger("no"), object.getBigDecimal("limit"));
				onw.put(object.getInteger("no"), object.getBigDecimal("onw"));
				team.put(object.getInteger("no"), object.getBigDecimal("team"));
				value.put(object.getInteger("no"), object.getBigDecimal("value"));
			});
		}
		// 获取所有符合条件未处理订单
		List<UserOrder> listUserOrder = userOrderService.list(Wrappers.<UserOrder>lambdaQuery()
			.eq(UserOrder::getPaid, 1)// 支付成功
			.ne(UserOrder::getPayType, 1)// 支付方式0平台余额1平台积分2众鸟余额
			.eq(UserOrder::getIsDispose, 0)//未处理订单
			.lt(UserOrder::getStatus, 1)//未收货
				//本月
			.between(UserOrder::getCreateTime, cn.hutool.core.date.DateUtil.beginOfMonth(cn.hutool.core.date.DateUtil.date()), cn.hutool.core.date.DateUtil.endOfMonth(cn.hutool.core.date.DateUtil.date()))
		);
		listUserOrder.forEach(order -> {
			// 获取用户信息
			User user = userService.getById(order.getUserId());
			// TODO 更新当前客户红包资格 当前订单金额与红包资格对比
			if (user.getBonusStatus() == 0 && order.getAwardBonus() == 1 && order.getPvTotalPrice().compareTo(repeat.get(user.getUserSign() == 0 ? 1 : user.getUserSign())) > -1) {
				System.out.println(">>>>>>>>>>>>>>>>>分配处理复消红包资格");
//				user.setBonusStatus(1);
//				userService.updateById(user);
				userService.bonusStatus(1, user.getId());
			}
			if (order.getPayType() == 2) {
//				order.setIsDispose(1);
//				userOrderService.updateById(order);
				userOrderService.dispose(order.getId());
			}
		});
		LykjJobHelper.log("红包资格定时任务。。。。。。");
	}

	/**--------------------------------------------------------------------------订单处理定时任务-----------------------------------------------------------------------------------------**/

	//每个月一号凌晨执行一次
	@Scheduled(cron = "0 0 0 1 * ?")
	public void orderDisposeJobHandler() throws Exception {
		//清空所有用户的红包资格
		userService.bonusStatus(0);
	}


	/**
	 * TODO 订单处理定时任务 每5分钟执行一次
	 */
//	@LykjJob("disposeOrderJobHandler")
	@Scheduled(cron = "0 */5 * * * ?")
	public void disposeOrderJobHandler() throws Exception {
		LykjJobHelper.log("订单处理定时任务开始。。。。。。");
		/**
		 // 获取相应规则
		 JSONArray memberSystemRule = JSONArray.parseArray(ParamCache.getValue("member.system.rule"));
		 if (memberSystemRule instanceof JSONArray) {
		 memberSystemRule.stream().forEach(x -> {
		 JSONObject object = (JSONObject) x;
		 num.put(object.getInteger("no"), object.getInteger("num"));
		 repeat.put(object.getInteger("no"), object.getBigDecimal("repeat"));
		 limit.put(object.getInteger("no"), object.getBigDecimal("limit"));
		 onw.put(object.getInteger("no"), object.getBigDecimal("onw"));
		 team.put(object.getInteger("no"), object.getBigDecimal("team"));
		 value.put(object.getInteger("no"), object.getBigDecimal("value"));
		 });
		 }
		 // 获取所有符合条件未处理订单
		 List<UserOrder> listUserOrder = userOrderService.list(Wrappers.<UserOrder>lambdaQuery()
		 .eq(UserOrder::getPaid, 1)// 支付成功
		 .ne(UserOrder::getPayType, 1)// 支付方式0平台余额1平台积分2众鸟余额
		 .eq(UserOrder::getIsDispose, 0)//未处理订单
		 .eq(UserOrder::getStatus, 1)//已收货
		 );
		 listUserOrder.forEach(order -> {
		 //更改处理状态
		 //			order.setIsDispose(1);
		 //			userOrderService.updateById(order);
		 userOrderService.dispose(order.getId());
		 // 获取用户信息
		 User user = userService.getById(order.getUserId());
		 //			user.setOrdersTotal(user.getOrdersTotal().add(order.getPvTotalPrice()));
		 userService.inOrdersTotal(order.getPvTotalPrice(),user.getId());

		 // 判断当前用户订单数量
		 Integer count = userOrderService.list(Wrappers.<UserOrder>lambdaQuery()
		 .eq(UserOrder::getUserId, order.getUserId())
		 .eq(UserOrder::getPaid, 1)// 支付成功
		 .ne(UserOrder::getPayType, 1)// 支付方式0平台余额1平台积分2众鸟余额
		 ).size();
		 // 如果是第一单，并且跨月收货，多送一次红包资格
		 if (count <= 1 && user.getBonusStatus()==0) {
		 //				user.setBonusStatus(1);
		 userService.bonusStatus(1,user.getId());
		 }
		 //将红包类商品金额更新当前客户累计消费金额
		 if (order.getAwardBonus() == 1) {
		 //				user.setBonusOrders(user.getBonusOrders().add(order.getPvTotalPrice()));
		 userService.inBonusOrders(order.getPvTotalPrice(),user.getId());
		 }
		 // TODO 判断是否有推荐人
		 if (user.getSpreadId() != null || user.getSpreadId() != 0L) {
		 //获取推荐人信息
		 User referrer = userService.getOne(new LambdaQueryWrapper<User>().eq(User::getUid, user.getSpreadId()));
		 BigDecimal referrerBalance = referrer.getSysBalance();
		 BigDecimal referrerIntegral = referrer.getSysIntegral();
		 BigDecimal referrerContribute = referrer.getSysContribute();
		 if (referrer != null) {
		 // TODO 一.佣金类商品 上级直返5%现金收益
		 BigDecimal brokeragePrice = order.getPvTotalPrice().multiply(order.getBrokerageRatio());
		 if (order.getAwardBrokerage() == 1 && brokeragePrice.compareTo(BigDecimal.ZERO) > 0) {
		 // 上级直返5%现金收益
		 //						referrer.setSysBalance(referrer.getSysBalance().add(brokeragePrice));
		 //						userService.updateById(referrer);
		 userService.inBalance(brokeragePrice,referrer.getId());

		 referrerBalance = referrerBalance.add(brokeragePrice);
		 //佣金奖励记录
		 userBillService.insertBill(
		 referrer.getTenantId(),
		 referrer.getId(),
		 user.getId(),
		 order.getId(),
		 1,//0转出1转入
		 brokeragePrice,
		 BigDecimal.ZERO,
		 "推荐奖励",
		 0,//0现金1积分2贡献值
		 2,//0增加1减少2奖励3兑换4充值5提现6购物7转账8红包9收益10运费
		 referrerBalance,
		 "推荐奖励,订单[" + order.getId() + "],推荐[" + user.getId() + "],金额[" + brokeragePrice + "],手续费[" + BigDecimal.ZERO + "],实际到账[" + brokeragePrice + "],余额[" + referrerBalance + "]"
		 );
		 //						UserBill inBill = new UserBill();
		 //						inBill.setTenantId(order.getTenantId());
		 //						inBill.setUserId(referrer.getId());
		 //						inBill.setOtherUserId(user.getId());
		 //						inBill.setLinkId(order.getId());
		 //						inBill.setPm(1);//0转出1转入
		 //						inBill.setTitle("推荐奖励");
		 //						inBill.setCategory(0);//0现金1积分2贡献值
		 //						inBill.setType(2);//0增加1减少2奖励3兑换4充值5提现6购物7转账8红包9收益
		 //						inBill.setNumber(brokeragePrice);
		 //						inBill.setService(BigDecimal.ZERO);
		 //						inBill.setActual(inBill.getNumber().subtract(inBill.getService()));
		 //						inBill.setBalance(referrer.getSysBalance().add(brokeragePrice));
		 //						inBill.setRemark("推荐奖励,订单[" + order.getId() + "],推荐[" + user.getId() + "],金额[" + inBill.getNumber() + "],手续费[" + inBill.getService() + "],实际到账[" + inBill.getActual() + "],余额[" + inBill.getBalance() + "]");
		 //						userBillService.save(inBill);
		 }
		 // TODO 二.积分类商品
		 if (order.getAwardIntegral() == 1) {
		 // TODO 1.奖励推荐人首单积分 订单金额*奖励积分比例
		 if (count <= 1) {
		 BigDecimal integral = order.getPvTotalPrice();
		 if (integral.compareTo(referrer.getOrdersTotal()) > -1) {
		 //积分大于等于推荐人消费总额时，奖励当前推荐人消费金额相等积分
		 integral = referrer.getOrdersTotal();
		 }
		 //							referrer.setSysIntegral(referrer.getSysIntegral().add(integral));
		 //							userService.updateById(referrer);
		 userService.inIntegral(integral,referrer.getId());

		 referrerIntegral = referrerIntegral.add(integral);
		 //积分奖励记录
		 userBillService.insertBill(
		 referrer.getTenantId(),
		 referrer.getId(),
		 user.getId(),
		 order.getId(),
		 1,//0转出1转入
		 integral,
		 BigDecimal.ZERO,
		 "积分奖励",
		 1,//0现金1积分2贡献值
		 2,//0增加1减少2奖励3兑换4充值5提现6购物7转账8红包9收益10运费
		 referrerIntegral,
		 "第一单积分奖励,订单[" + order.getId() + "],积分[" + integral + "],手续费[" + BigDecimal.ZERO + "],实际到账[" + integral + "],余额[" + referrerIntegral + "]"
		 );
		 //							UserBill inBill = new UserBill();
		 //							inBill.setTenantId(order.getTenantId());
		 //							inBill.setUserId(referrer.getId());
		 //							inBill.setOtherUserId(user.getId());
		 //							inBill.setLinkId(order.getId());
		 //							inBill.setPm(1);//0转出1转入
		 //							inBill.setTitle("积分奖励");
		 //							inBill.setCategory(1);//0现金1积分2贡献值
		 //							inBill.setType(2);//0增加1减少2奖励3兑换4充值5提现6购物7转账8红包9收益
		 //							inBill.setNumber(integral);
		 //							inBill.setService(BigDecimal.ZERO);
		 //							inBill.setActual(inBill.getNumber().subtract(inBill.getService()));
		 //							inBill.setBalance(referrer.getSysIntegral());
		 //							inBill.setRemark("第一单积分奖励,订单[" + order.getId() + "],金额[" + inBill.getNumber() + "],手续费[" + inBill.getService() + "],实际到账[" + inBill.getActual() + "],余额[" + inBill.getBalance() + "]");
		 //							userBillService.save(inBill);
		 }
		 }
		 // TODO 三.赠送推荐人贡献值
		 if (order.getAwardContribute() == 1) {
		 JSONObject contributeValue = JSONObject.parseObject(ParamCache.getValue("contribute.value"));
		 if (contributeValue instanceof JSONObject) {
		 JSONArray rule = contributeValue.getJSONArray("rule");
		 if (rule instanceof JSONArray) {
		 //系数=贡献值现值/贡献值基质-1
		 BigDecimal multiple = contributeValue.getBigDecimal("now").divide(contributeValue.getBigDecimal("basics"), 2, BigDecimal.ROUND_DOWN).subtract(new BigDecimal(1));
		 AtomicReference<BigDecimal> ratio1 = new AtomicReference<>(BigDecimal.ZERO);
		 AtomicReference<BigDecimal> ratio2 = new AtomicReference<>(BigDecimal.ZERO);
		 for (int i = 0; i < rule.size(); i++) {
		 JSONObject object = rule.getJSONObject(i);
		 BigDecimal s = object.getJSONObject("multiple").getBigDecimal("s");
		 BigDecimal n = object.getJSONObject("multiple").getBigDecimal("n");
		 if (multiple.compareTo(s) > -1 && multiple.compareTo(n) < 1) {
		 BigDecimal m = object.getJSONObject("ratio").getBigDecimal("m");
		 BigDecimal c = object.getJSONObject("ratio").getBigDecimal("c");
		 ratio1.set(m);
		 ratio2.set(c);
		 break;
		 }
		 }
		 //在奖励区间范围 大于0才能获得积分
		 if (ratio1.get().compareTo(BigDecimal.ZERO) > 0) {
		 //奖励贡献值=订单价格/规则1*规则2
		 BigDecimal contribute = order.getPvTotalPrice().divide(ratio1.get(), 2, BigDecimal.ROUND_DOWN).multiply(ratio2.get());
		 if (contribute.compareTo(new BigDecimal(0)) > -1) {
		 //										referrer.setSysContribute(referrer.getSysContribute().add(contribute));
		 //										userService.updateById(referrer);
		 userService.inContribute(contribute,referrer.getId());

		 referrerContribute = referrerContribute.add(contribute);
		 //增加贡献值赠送记录
		 userBillService.insertBill(
		 referrer.getTenantId(),
		 referrer.getId(),
		 user.getId(),
		 order.getId(),
		 1,//0转出1转入
		 contribute,
		 BigDecimal.ZERO,
		 "贡献值奖励",
		 2,//0现金1积分2贡献值
		 2,//0增加1减少2奖励3兑换4充值5提现6购物7转账8红包9收益10运费
		 referrerContribute,
		 "贡献值奖励,订单[" + order.getId() + "],推荐[" + user.getId() + "],贡献值[" + contribute + "],手续费[" + BigDecimal.ZERO + "],实际到账[" + contribute + "],余额[" + referrerContribute + "]"
		 );
		 //										UserBill inBill = new UserBill();
		 //										inBill.setTenantId(order.getTenantId());
		 //										inBill.setUserId(referrer.getId());
		 //										inBill.setOtherUserId(user.getId());
		 //										inBill.setLinkId(order.getId());
		 //										inBill.setPm(1);//0转出1转入
		 //										inBill.setTitle("贡献值奖励");
		 //										inBill.setCategory(2);//0现金1积分2贡献值
		 //										inBill.setType(2);//0增加1减少2奖励3兑换4充值5提现6购物7转账8红包9收益
		 //										inBill.setNumber(contribute);
		 //										inBill.setService(BigDecimal.ZERO);
		 //										inBill.setActual(inBill.getNumber().subtract(inBill.getService()));
		 //										inBill.setBalance(referrer.getSysContribute());
		 //										inBill.setRemark("贡献值奖励,订单[" + order.getId() + "],推荐[" + user.getId() + "],金额[" + inBill.getNumber() + "],手续费[" + inBill.getService() + "],实际到账[" + inBill.getActual() + "],余额[" + inBill.getBalance() + "]");
		 //										userBillService.save(inBill);
		 }
		 }
		 }
		 }
		 }
		 }
		 }
		 // TODO 五.普通会员升级VIP
		 if (user.getUserSign() == 0 && order.getPvTotalPrice().compareTo(onw.get(1)) > -1 && user.getUserSign() == 0) {
		 System.out.println(">>>>>>>>>>>>>>>>>普通会员升级");
		 user.setUserSign(1);
		 }
		 // TODO 六.服务收益（极差收益）
		 if (order.getAwardRange() == 1) {
		 System.out.println(">>>>>>>>>>>>>>>>>服务收益（极差收益）");
		 //				updateTeamRevenue(user.getSpreadId(), user.getUserSign(), order.getPvTotalPrice(), order.getId());
		 updateTeamRevenue(user.getSpreadId(), 0, order.getPvTotalPrice(), order.getId());
		 }
		 //			userService.updateById(user);
		 });
		 **/
		LykjJobHelper.log("订单处理定时任务结束。。。。。。");
	}

	/**
	 * 服务收益-极差收益（奖励现金）
	 * 从下往上单线返到顶级，同级跳过继续往上
	 *
	 * @param spreadId   上级用户ID
	 * @param downLevel  用户级别
	 * @param orderPrice 订单价格
	 * @return
	 */
	private BigDecimal updateTeamRevenue(Long spreadId, int downLevel, BigDecimal orderPrice, Long oid) {
		BigDecimal revenue = BigDecimal.ZERO;
		System.out.println("服务收益-极差收益（奖励现金）0>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>spreadId：" + spreadId + ",downLevel:" + downLevel + "orderPrice:" + orderPrice + ",oid:" + oid);
		User userTemp = userService.getOne(new LambdaQueryWrapper<User>().eq(User::getUid, spreadId));
//		BigDecimal userBalance = userTemp.getSysBalance();
		if (userTemp != null) {
			if (downLevel < userTemp.getUserSign()) {
				if (downLevel == 0) {
					downLevel = 1;
				}
				// 当前用户服务收益（级别对应系数*订单金额）-下级服务收益（级别对应系数*订单金额）
				revenue = value.get(userTemp.getUserSign()).multiply(orderPrice).subtract(value.get(downLevel).multiply(orderPrice));
				// 去掉超限金额
				if (revenue.compareTo(limit.get(downLevel)) > 0) {
					revenue = limit.get(downLevel);
				}
				System.out.println("服务收益-极差收益（奖励现金）2>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>" + userTemp.getUserSign() + ":" + revenue);
				// 极差收益大于零 分配奖励
				if (revenue.compareTo(BigDecimal.ZERO) > 0) {
//					userTemp.setEarningsTotal(userTemp.getEarningsTotal().add(revenue));
//					userTemp.setSysBalance(userTemp.getSysBalance().add(revenue));
//					userService.updateById(userTemp);
					//增加收益
					userService.inEarningsTotal(revenue, userTemp.getId());

//					userBalance = userBalance.add(revenue);
					//服务收益奖励记录
					userBillService.insertBill(
						userTemp.getTenantId(),
						userTemp.getId(),
						0L,
						oid,
						1,//0转出1转入
						revenue,
						BigDecimal.ZERO,
						"服务收益",
						0,//0现金1积分2贡献值
						9,//0增加1减少2奖励3兑换4充值5提现6购物7转账8红包9收益10运费
//						userBalance,
						"服务收益,订单[" + oid + "],推荐[" + userTemp.getId() + "],金额[" + revenue + "],手续费[" + BigDecimal.ZERO + "],实际到账[" + revenue + "]"//,余额[" + userBalance + "]
					);
//					UserBill inBill = new UserBill();
//					inBill.setTenantId(userTemp.getTenantId());
//					inBill.setUserId(userTemp.getId());
//					inBill.setOtherUserId(0L);
//					inBill.setLinkId(oid);
//					inBill.setPm(1);//0转出1转入
//					inBill.setTitle("服务收益");
//					inBill.setCategory(0);//0现金1积分2贡献值
//					inBill.setType(9);//0增加1减少2奖励3兑换4充值5提现6购物7转账8红包9收益
//					inBill.setNumber(revenue);
//					inBill.setService(BigDecimal.ZERO);
//					inBill.setActual(inBill.getNumber().subtract(inBill.getService()));
//					inBill.setBalance(userTemp.getSysBalance());
//					inBill.setRemark("服务收益,订单[" + oid + "],推荐[" + userTemp.getId() + "],金额[" + inBill.getNumber() + "],手续费[" + inBill.getService() + "],实际到账[" + inBill.getActual() + "],余额[" + inBill.getBalance() + "]");
//					userBillService.save(inBill);
				}
			}
			System.out.println("服务收益-极差收益（奖励现金）3>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>" + userTemp.getUserSign() + ":" + userTemp.getSpreadId());
			if (userTemp.getSpreadId() != null && userTemp.getSpreadId() != 0 && userTemp.getUserSign() < 5) {
				updateTeamRevenue(userTemp.getSpreadId(), (downLevel > userTemp.getUserSign() ? downLevel : userTemp.getUserSign()), orderPrice, oid);
			}
		}
		return revenue;
	}

	/**--------------------------------------------------------------------------会员升级定时任务-----------------------------------------------------------------------------------------**/

	/**
	 * TODO 会员升级定时任务 每5分钟执行一次
	 */
//	@LykjJob("memberUpgradeJobHandler")
	@Scheduled(cron = "0 */5 * * * ?")
	public void memberUpgradeJobHandler() throws Exception {
		LykjJobHelper.log("会员升级定时任务开始。。。。。。");
		// 获取相应规则
		JSONArray memberSystemRule = JSONArray.parseArray(ParamCache.getValue("member.system.rule"));
		if (memberSystemRule instanceof JSONArray) {
			memberSystemRule.stream().forEach(x -> {
				JSONObject object = (JSONObject) x;
				num.put(object.getInteger("no"), object.getInteger("num"));
				repeat.put(object.getInteger("no"), object.getBigDecimal("repeat"));
				limit.put(object.getInteger("no"), object.getBigDecimal("limit"));
				onw.put(object.getInteger("no"), object.getBigDecimal("onw"));
				team.put(object.getInteger("no"), object.getBigDecimal("team"));
				value.put(object.getInteger("no"), object.getBigDecimal("value"));
			});
		}
		List<User> list = userService.list(new LambdaQueryWrapper<User>()
				.eq(User::getUserType, 2)
//			.gt(User::getUserSign, 0) //收益级别大于0的会员
//			.lt(User::getUserSign, 5) //收益级别小于5的会员
		);
		list.forEach(u -> {
			System.out.println("会员【" + u.getUid() + "】开始升级......，当前级别：" + u.getUserSign());
			// 0普通会员
			// 1VIP  单笔消费3600
			// 2店长 个人订单总额>=10800，会员级别为1，小团队业绩达到108000以上，直推两个VIP会员
			// 3精英 个人订单总额>=21600，会员级别为2，小团队业绩达到360000以上，培育直推的社区店长两个以上
			// 4导师 个人订单总额>=36000，会员级别为3，小团队业绩达到1080000以上，培育直接推荐的创客精英三个以上
			// 5领袖 个人订单总额>=49600，会员级别为4，小团队业绩达到3600000以上，培育直推四个创客导师以上
			if (u.getUserSign() == 0 || u.getUserSign() == 5) {
				System.out.println("会员【" + u.getUid() + "】升级中......，当前级别不需要升级：" + u.getUserSign());
				return;
			}
			// 判断个人消费总额是否达到升级上级所需个人消费对应的消费总额
			BigDecimal bonusOrders = userOrderService.bonusOrdersTotal(u.getId());
			if (bonusOrders.compareTo(onw.get(u.getUserSign() + 1)) < -0) {
				System.out.println("会员【" + u.getUid() + "】升级中......，个人消费总额未达标：" + bonusOrders);
				return;
			}
			System.out.println("会员【" + u.getUid() + "】升级中......，个人消费总额达标：" + bonusOrders);
//			if (u.getBonusOrders().compareTo(onw.get(u.getUserSign() + 1)) < -0) {
//				System.out.println("会员【" + u.getUid() + "】升级中......，个人消费总额未达标：" + u.getBonusOrders());
//				return;
//			}
//			System.out.println("会员【" + u.getUid() + "】升级中......，个人消费总额达标：" + u.getBonusOrders());
			// 判断小团队总业绩是否达标
			if (getTeamNorm(list, u.getUid(), u.getUserSign(), num.get(u.getUserSign() + 1), userOrderService)) {
				System.out.println("会员【" + u.getUid() + "】升级中......，小团队总业绩达标,升一级");
//				u.setUserSign(u.getUserSign() + 1);
//				userService.updateById(u);
				userService.upgrade(u.getId());
			}
			System.out.println("会员【" + u.getUid() + "】结束升级......，当前级别：" + u.getUserSign());
		});
		LykjJobHelper.log("会员升级定时任务结束。。。。。。");
	}

	/**
	 * 判断小团队总业绩是否达标
	 *
	 * @param list  会员列表
	 * @param uid   当前人员ID
	 * @param level 当前人员级别
	 * @param num   升级所需下级数量
	 * @return
	 */
	private static boolean getTeamNorm(List<User> list, Long uid, int level, int num, UserOrderService userOrderService) {
		//小团队消费总额
		BigDecimal tb = team.get(level + 1);
		System.out.println("会员【" + uid + "】升级中......，小团队总业绩升级要求：" + tb + ",进入list数量：" + list.size());
		//1、获取直接下级会员
		List<User> tempList = list.stream().filter(s -> (uid.equals(s.getSpreadId()))).collect(Collectors.toList());
		System.out.println("会员【" + uid + "】升级中......，下级会员数量：" + tempList.size());
		if (tempList != null && tempList.size() > 0) {
			//判断下级会员数量是否达到升级要求 达到相同级别 几个 及以上
			Long numTemp = tempList.stream().filter(t -> (t.getUserSign() >= level)).count();
			System.out.println("会员【" + uid + "】升级中......，下级会员符合升级要求会员数量：" + numTemp + ",升级要求数量：" + num);
			if (num > numTemp.intValue()) {
				return false;
			}
			// 未达标小团队消费总额
			BigDecimal totalOrders = BigDecimal.ZERO;
			boolean b = false;
			//循环下级所有会员
			for (User u : tempList) {
				// 加上自己的消费总额
				BigDecimal temp = getTeamOrdersPrice(list, u.getUid(), userOrderService);
				BigDecimal bonusOrders = userOrderService.bonusOrdersTotal(u.getId());
				temp = temp.add(bonusOrders);
//				temp = temp.add(u.getBonusOrders());
				System.out.println("会员【" + uid + "】升级中......，小团队【" + u.getUid() + "】消费总额：" + temp);
				if (b == false && temp.compareTo(tb) > -1) {
					System.out.println("会员【" + uid + "】升级中......，小团队【" + u.getUid() + "】消费总额达标：" + temp);
					b = true;
				} else {
					totalOrders = totalOrders.add(temp);
				}
			}
			System.out.println("会员【" + uid + "】升级中......，剩余小团队消费总额：" + totalOrders);
			if (b && totalOrders.compareTo(tb) > -1) {
				System.out.println("会员【" + uid + "】升级中......，剩余小团队消费总额达标：" + totalOrders);
				return true;
			}
		}
		return false;
	}

	/**
	 * 获取团队消费总额（从上往下，所有成员不包含自己）
	 *
	 * @param uid 用户uid
	 * @return
	 */
	private static BigDecimal getTeamOrdersPrice(List<User> list, Long uid, UserOrderService userOrderService) {
		BigDecimal totalOrders = BigDecimal.ZERO;
		List<User> tempList = list.stream().filter(s -> (uid.equals(s.getSpreadId()))).collect(Collectors.toList());
		if (tempList != null && tempList.size() > 0) {
			for (User u : tempList) {
				BigDecimal bonusOrders = userOrderService.bonusOrdersTotal(u.getId());
				totalOrders = totalOrders.add(bonusOrders).add(getTeamOrdersPrice(list, u.getUid(), userOrderService));
//				totalOrders = totalOrders.add(u.getBonusOrders()).add(getTeamOrdersPrice(list, u.getUid()));
			}
		}
		return totalOrders;
	}

	/**--------------------------------------------------------------------------发放收益定时任务-----------------------------------------------------------------------------------------**/

	/**
	 * TODO 发放收益定时任务	每天 00:00:01 开始执行
	 */
//	@LykjJob("grantBonusJobHandler")
	@Scheduled(cron = "1 31 11 * * ?")
	public void grantBonusJobHandler() throws Exception {
		LykjJobHelper.log("发放收益定时任务开始。。。。。。");
		JSONObject bonusRuleJson = null;
		String tenantId = "000000";
		String pvValue = ParamCache.getValue("pv.number");
		// 获取红包日历
		JSONArray bonusCalendar = JSONArray.parseArray(ParamCache.getValue(tenantId + ".bonus.calendar"));
		for (int i = 0; i < bonusCalendar.size(); i++) {
			JSONObject object = (JSONObject) bonusCalendar.get(i);
			if (DateUtil.format(new Date(), DateUtil.PATTERN_DATE).equals(object.getString("date"))) {
				bonusRuleJson = object.getJSONObject("rule");
			}
		}
		System.out.println("0、红包规则：" + bonusRuleJson.toJSONString());
		if (bonusRuleJson instanceof JSONObject) {
			BigDecimal le = new BigDecimal(bonusRuleJson.get("le").toString());// 1/36
			BigDecimal ge = new BigDecimal(bonusRuleJson.get("ge").toString());// 1/72

			System.out.println("1、符合规则进入红包过程，规则le(1/36)：" + le + "，规则ge(1/72)" + ge);
			List<UserOrder> listUserOrder = userOrderService.list(Wrappers.<UserOrder>lambdaQuery()
				.eq(UserOrder::getPaid, 1)// 支付成功
				.ne(UserOrder::getPayType, 1)// 支付方式0平台余额1平台积分2众鸟余额
				.eq(UserOrder::getAwardBonus, 1)// 红包产品
				.eq(UserOrder::getStopBonus, 0)//未停止红包
				.eq(UserOrder::getStatus, 1)//已收货
			);
			listUserOrder.forEach(order -> {
				try{
					System.out.println("2、符合订循环过程，订单号：" + order.getId() + "，订单金额：" + order.getPvTotalPrice());
					// 获取用户信息
					User user = userService.getById(order.getUserId());
					// 判断红包资格
					if (user.getBonusStatus() != 1) {
						return; // 跳出当前循环,继续下一轮
					}
					// 同一个订单如有未领取的当天不再发放
					Integer count = userBonusService.list(Wrappers.<UserBonus>lambdaQuery()
							.eq(UserBonus::getStatus, 0)//未领取
							.eq(UserBonus::getOrderId, order.getId())//订单ID
							.eq(UserBonus::getUserId, order.getUserId())//会员ID
	//					.notLike(UserBonus::getCreateTime, LykjDateUtils.getDate())//不包含当天的
					).size();
					if (count > 0) {
						return; // 跳出当前循环,继续下一轮
					}
					System.out.println("2.1、符合订循环过程，订单号：" + order.getId() + "，没有重复发放订单");
					//红包金额
					BigDecimal bonus = BigDecimal.ZERO;
					// 开始赠送红包-红包规则
					// 红包规则：{"le":0.0277,"ge":0.0138,"two":0}
					// @TODO 订单消费额 * 2 > 累计红包时继续红包，否则不红包
					BigDecimal orderTotalBonus = userBonusService.bonusTotalByOrder(order.getId());
					//if () {//order.getTotalBonus()
					// @TODO 订单消费额超过50000时继续红包，否则不红包
					System.out.println("2.2、符合订循环过程，(order.getPvTotalPrice().multiply(BigDecimal.valueOf(2)).compareTo(orderTotalBonus) > 0" + (order.getPvTotalPrice().multiply(BigDecimal.valueOf(2)).compareTo(orderTotalBonus) > 0));
					System.out.println("超过设定PV值"+pvValue+"时继续红包，否则不红包");
					if ((order.getPvTotalPrice().multiply(BigDecimal.valueOf(2)).compareTo(orderTotalBonus) > 0&&order.getUpdateTime().before(DateUtil.parse("2022-07-15", DateUtil.PATTERN_DATE)))||
							order.getPvTotalPrice().compareTo(BigDecimal.valueOf(Long.parseLong(pvValue))) > 0) {
						System.out.println("2.2、符合订循环过程，订单号：" + order.getId() + "，订单金额*2大于累计红包");
						// @TODO 累计红包>订单金额 && <2倍订单金额时 = ge0.0138（1/72），累计红包 < 订单金额时 = le0.0277（1/36）
						if (order.getPvTotalPrice().compareTo(orderTotalBonus) > -1) {//order.getTotalBonus()
							bonus = order.getPvTotalPrice().multiply(le);
							System.out.println("2.3、符合订循环过程，订单号：" + order.getId() + "，订单金额大于等于累计红包取1/36，红包金额：" + bonus);
						} else {
							bonus = order.getPvTotalPrice().multiply(ge);
							System.out.println("2.3、符合订循环过程，订单号：" + order.getId() + "，订单金额小于等于累计红包取1/72，红包金额：" + bonus);
						}
					} else {
						System.out.println("2.4、符合订循环过程，订单号：" + order.getId() + "，订单金额*2小于累计红包，停止红包");
						// @TODO 单个订单的红包累计金额是1000，若该笔订单金额是500或者该笔订单金额小于500，这笔订单不再红包
	//					order.setStopBonus(1);
	//					userOrderService.updateById(order);
						userOrderService.stopBonus(order.getId());
						return; // 跳出当前循环,继续下一轮
					}
					System.out.println("2.5、符合订循环过程，订单号：" + order.getId() + "，计算红包金额：" + bonus);
					if (bonus.compareTo(BigDecimal.ZERO) == 1) {
						// 添加未领取状态的红包记录
						UserBonus userBonus = new UserBonus();
						userBonus.setTenantId(order.getTenantId());
						userBonus.setTitle("工作日红包");
						// 验证日发放金额是否超过750
						BigDecimal bonusLimit = BigDecimal.valueOf(750);
						// 判断个人是否设置红包上限
						if (user.getBonusLimit().compareTo(BigDecimal.ZERO) > 0) {
							bonusLimit = user.getBonusLimit();
						}
						// 获取当天已发放红包
						List<UserBonus> listUserCoupon = userBonusService.list(new LambdaQueryWrapper<UserBonus>()
							.eq(UserBonus::getUserId, order.getUserId())
							.like(UserBonus::getCreateTime, DateUtil.format(new Date(), DateUtil.PATTERN_DATE))
						);
						// 根据当天已发放红包 判断是否重复发放
						Long countBonus = listUserCoupon.stream().filter(s -> s.getOrderId().equals(order.getId())).count();
						if (countBonus != 0) {
							return; // 跳出当前循环,继续下一轮
						}
						// 当天已发放总额
						BigDecimal bonusNumberSum = listUserCoupon.stream().map(e -> e.getNumber()).reduce(BigDecimal.ZERO, BigDecimal::add);
						// 当天发放总额是否超限
						if (bonusNumberSum.compareTo(bonusLimit) > -1) {
							bonus = BigDecimal.ZERO;
							userBonus.setTitle("工作日红包-超限");
						} else {
							if (bonus.add(bonusNumberSum).compareTo(bonusLimit) > -1) {
								bonus = bonusLimit.subtract(bonusNumberSum);
								userBonus.setTitle("工作日红包-超限");
							}
						}
						userBonus.setUserId(order.getUserId());
						userBonus.setOrderId(order.getId());
						userBonus.setNumber(bonus);
						userBonus.setRemark("会员[" + user.getId() + "],订单：[" + order.getId() + "],订单PV值[" + order.getPvTotalPrice() + "],红包[" + bonus + "]");
						userBonus.setStatus(0);
						userBonusService.save(userBonus);
	//					userOrderService.totalBonus(bonus, order.getId());
					}
				}catch (Exception e) {
					e.printStackTrace();
					System.out.println("1234567890"+e);
				}
			});
		}
		LykjJobHelper.log("发放收益定时任务结束。。。。。。");
	}

	public static void main(String[] args) {
		JSONArray jsonArray = new JSONArray();
		JSONObject bonusRuleJson = new JSONObject();
		bonusRuleJson.put("1", "11");
		jsonArray.add(bonusRuleJson);

		bonusRuleJson = new JSONObject();
		bonusRuleJson.put("1", "22");
		jsonArray.add(bonusRuleJson);

		bonusRuleJson = new JSONObject();
		bonusRuleJson.put("1", "33");
		jsonArray.add(bonusRuleJson);

		bonusRuleJson = new JSONObject();
		bonusRuleJson.put("1", "44");
		jsonArray.add(bonusRuleJson);

		bonusRuleJson = new JSONObject();
		bonusRuleJson.put("1", "55");
		jsonArray.add(bonusRuleJson);

//		jsonArray.stream().anyMatch(x -> {
//			JSONObject object = (JSONObject) x;
//			if (object.get("1") == "11") {
//				Predicate.isEqual(x);
//				System.out.println(object);
//				return true;
//			}
//			System.out.println(object);
//			return false;
//		});

		jsonArray.stream().forEach(x -> {
			JSONObject object = (JSONObject) x;
			if (object.get("1") == "33") {
				return;
			}
			System.out.println(object);
		});
//		System.out.println(jsonArray);
//		for(int i=0;i<jsonArray.size();i++){
//			JSONObject object = jsonArray.getJSONObject(i);
//			System.out.println(object);
//		}
	}
}
